package app

import (
	"APT/internal/dao"
	"APT/internal/library/contexts"
	"APT/internal/model"
	"APT/internal/model/entity"
	"APT/internal/model/input/input_basics"
	"APT/internal/service"
	"APT/utility/encrypt"
	"context"
	"database/sql"
	"errors"
	"fmt"
	"github.com/gogf/gf/v2/container/gvar"
	"github.com/gogf/gf/v2/frame/g"
	"github.com/gogf/gf/v2/os/gtime"

	"github.com/gogf/gf/v2/errors/gerror"

	"APT/api/app/member"
)

func (c *ControllerMember) GetUserInfo(ctx context.Context, _ *member.GetUserInfoReq) (res *member.GetUserInfoRes, err error) {
	var (
		UserInfo *model.MemberIdentity
	)
	UserInfo = contexts.GetMemberUser(ctx)
	res = new(member.GetUserInfoRes)
	if err = g.Model(dao.PmsMember.Table()).Ctx(ctx).WithAll().Where(dao.PmsMember.Columns().Id, UserInfo.Id).Scan(&res); err != nil && !errors.Is(err, sql.ErrNoRows) {
		return
	}
	return
}

func (c *ControllerMember) BindEmail(ctx context.Context, req *member.BindEmailReq) (res *member.BindEmailRes, err error) {
	var (
		MemberContextInfo = contexts.GetMemberUser(ctx)
		MemberInfo        *entity.PmsMember
	)
	if err = dao.PmsMember.Ctx(ctx).Where(dao.PmsMember.Columns().Id, MemberContextInfo.Id).Scan(&MemberInfo); err != nil {
		return
	}
	if g.IsEmpty(MemberInfo) {
		err = gerror.New("用户信息不存在")
		return
	}
	// 验证邮箱验证码
	if err = service.BasicsEmsLog().VerifyCode(ctx, &input_basics.VerifyEmsCodeInp{
		Event: "login",
		Email: req.Email,
		Code:  req.Code,
	}); err != nil {
		return
	}

	// 查询是否已存在该邮箱用户
	value, err := dao.PmsMember.Ctx(ctx).Where(dao.PmsMember.Columns().Mail, req.Email).Value(dao.PmsMember.Columns().Id)
	if err != nil {
		return nil, err
	}
	if !value.IsEmpty() {
		err = gerror.New("该邮箱已被占用，无法绑定")
		return
	}
	// 更新邮箱数据到会员表中
	if _, err = dao.PmsMember.Ctx(ctx).Where(dao.PmsMember.Columns().Id, MemberContextInfo.Id).Update(g.MapStrAny{
		dao.PmsMember.Columns().Mail: req.Email,
	}); err != nil {
		return
	}
	return
}

func (c *ControllerMember) BindPhone(ctx context.Context, req *member.BindPhoneReq) (res *member.BindPhoneRes, err error) {
	var (
		MemberContextInfo = contexts.GetMemberUser(ctx)
		MemberInfo        *entity.PmsMember
		MobileNo          string
		smsEvent          string
	)
	// 查询用户是否存在
	if err = dao.PmsMember.Ctx(ctx).Where(dao.PmsMember.Columns().Id, MemberContextInfo.Id).Scan(&MemberInfo); err != nil {
		return
	}
	if g.IsEmpty(MemberInfo) {
		err = gerror.New("用户信息不存在")
		return
	}

	switch req.AreaNo {
	case "+81":
		smsEvent = "login-ja"
		MobileNo = fmt.Sprintf("%s%s", req.AreaNo, req.Phone)
		break
	case "+82":
		smsEvent = "login-ko"
		MobileNo = fmt.Sprintf("%s%s", req.AreaNo, req.Phone)
		break
	case "+86":
		smsEvent = "login"
		MobileNo = fmt.Sprintf("%s%s", req.AreaNo, req.Phone)
		break
	default:
		smsEvent = "login-en"
		MobileNo = fmt.Sprintf("%s%s", req.AreaNo, req.Phone)
		break
	}

	// 查询是否存在该手机号
	value, err := dao.PmsMember.Ctx(ctx).Where(g.MapStrAny{
		dao.PmsMember.Columns().Phone:     req.Phone,
		dao.PmsMember.Columns().PhoneArea: req.AreaNo,
	}).Value(dao.PmsMember.Columns().Id)
	if err != nil {
		return nil, err
	}
	if !value.IsEmpty() {
		err = gerror.New("该手机号已被占用，无法绑定")
		return
	}

	if err = service.BasicsSmsLog().VerifyCode(ctx, &input_basics.VerifyCodeInp{
		Event:  smsEvent,
		Mobile: MobileNo,
		Code:   req.Code,
	}); err != nil {
		return
	}

	// 更新会员你手机号信息
	if _, err = dao.PmsMember.Ctx(ctx).Where(dao.PmsMember.Columns().Id, MemberContextInfo.Id).Update(g.MapStrAny{
		dao.PmsMember.Columns().Phone:     req.Phone,
		dao.PmsMember.Columns().PhoneArea: req.AreaNo,
	}); err != nil {
		return
	}
	return
}

func (c *ControllerMember) StaffInfo(ctx context.Context, req *member.StaffInfoReq) (res *member.StaffInfoRes, err error) {
	res = new(member.StaffInfoRes)
	if err = dao.PmsStaff.Ctx(ctx).Where(dao.PmsStaff.Columns().Id, req.StaffId).Scan(&res); err != nil {
		return
	}
	return
}
func (c *ControllerMember) ChannelInfo(ctx context.Context, req *member.ChannelInfoReq) (res *member.ChannelInfoRes, err error) {
	res = new(member.ChannelInfoRes)
	if err = dao.PmsChannel.Ctx(ctx).Where(dao.PmsChannel.Columns().Id, req.ChannelId).Scan(&res); err != nil {
		return
	}
	return
}

func (c *ControllerMember) UserLevelRule(ctx context.Context, _ *member.UserLevelRuleReq) (res *member.UserLevelRuleRes, err error) {
	var (
		MemberLevelMap *input_basics.GetConfigModel
	)
	MemberLevelMap = new(input_basics.GetConfigModel)
	if MemberLevelMap, err = service.BasicsConfig().GetConfigByGroup(ctx, &input_basics.GetConfigInp{
		Group: "memberlevel",
	}); err != nil {
		return
	}
	res = new(member.UserLevelRuleRes)
	res.LevelRule = gvar.New(MemberLevelMap.List["rule_"+contexts.GetLanguage(ctx)]).String()
	return
}

func (c *ControllerMember) EditUserInfo(ctx context.Context, req *member.EditUserInfoReq) (res *member.EditUserInfoRes, err error) {
	var (
		MemberUser   = contexts.GetMemberUser(ctx)
		orm          = g.Model(dao.PmsMember.Table()).Ctx(ctx).Safe()
		updateResult sql.Result
		updateRow    int64
	)
	res = new(member.EditUserInfoRes)
	if g.IsEmpty(req.FullName) && (!g.IsEmpty(req.FirstName) || !g.IsEmpty(req.LastName)) {
		req.FullName = fmt.Sprintf("%s %s", req.FirstName, req.LastName)
	}
	updateData := &entity.PmsMember{
		Avatar:      req.Avatar,
		Sex:         req.Sex,
		FirstName:   req.FirstName,
		LastName:    req.LastName,
		FullName:    req.FullName,
		Birthday:    gtime.New(req.Birthday),
		Nationality: req.Nationality,
		Password:    encrypt.Md5([]byte(req.Password)),
		Mail:        req.Email,
		Replenish:   "Y",
	}
	if updateResult, err = orm.Where(dao.PmsMember.Columns().Id, MemberUser.Id).OmitEmptyData().Update(updateData); err != nil {
		return
	}
	if updateRow, err = updateResult.RowsAffected(); err != nil {
		return
	}
	if updateRow == 0 {
		err = gerror.New("用户信息无改动")
		return
	}
	if updateRow != 1 {
		err = gerror.New("补全用户信息失败")
		return
	}
	return
}
